enum ContentType {
	json = 'application/json;charset=UTF-8',
	form = 'application/x-www-form-urlencoded; charset=UTF-8',
}

enum HttpMethod {
	get = 'GET',
	post = 'POST',
	put = 'PUT',
	patch = 'PATCH',
	delete = 'DELETE',
}

interface IHeader {
	'Content-Type'?: string
	'X-Requested-With'?: string
	token?: string

	[propName: string]: any
}

interface RequestConfig {
	body?: any
	method?: string
	headers?: IHeader
	token?: string
	'Content-Type'?: string
}

const myFetch = (url: string, config?: RequestConfig) => {
	return new Promise(async (resolve, reject) => {
		let promise: Response, contentType: string

		if (config?.['Content-Type'] !== undefined) {
			contentType = config['Content-Type']
		} else if (config?.method === HttpMethod.post) {
			contentType = ContentType.form
		} else {
			contentType = ContentType.json
		}

		const parseResult = async (res: Response) => {
			const contentType = res.headers.get('Content-Type')
			if (contentType) {
				if (contentType.indexOf('json') !== -1) return await res.json()
				if (contentType.indexOf('text') !== -1) return await res.text()
				if (contentType.indexOf('form') !== -1)
					return await res.formData()
				if (contentType.indexOf('video') !== -1) return await res.blob()
			}
			return res.text()
		}

		const handleResult = async (res: Response) => {
			const result = await parseResult(res)
			if (res.ok) return result
		}

		// const requestUrl = (baseUrl + url).replace('//', '/')
		const requestUrl = url
		const headers: Headers = new Headers({
			// token:
			// 	config?.token === undefined
			// 		? getLocalStorage('token')
			// 		: config.token,
			// 'Content-Type': contentType,
		} as IHeader)

		try {
			if (!config?.method || config.method === HttpMethod.get) {
				promise = await fetch(requestUrl, {
					headers,
				})
			} else if (config.method === HttpMethod.post) {
				promise = await fetch(requestUrl, {
					body: JSON.stringify(config.body),
					headers,
					method: HttpMethod.post,
				})
			} else {
				promise = await fetch(requestUrl, {
					body: JSON.stringify(config.body),
					headers,
					method: config.method,
				})
			}
			resolve(handleResult(promise))
		} catch (err) {
			console.error('fetch error!', err)
			reject(err)
		}
	})
}

export default myFetch
